
/// 联合 转 交叉
export type Union_as_xx<U> = (U extends any ? (x: U) => void : never) extends (
	x: infer R
) => void ? R : never;
/// 获取函数返回类型
export type GetReturnType<Type> = Type extends (...args: never[]) => infer Return
	? Return
	: never;

/// 获取函数第一个参数
export type GetArg1<Type> = Type extends (t:infer A,...args:never[])=>any ? A : never;

// /**
//  * 异常处理模块
//  */
// export module Result{
// 	export type Tag_Data<Tag,Data> = {
// 		tag:Tag,
// 		data:Data
// 	}
//
// 	export type Err<E> = Tag_Data<"Err", E>;
// 	export function Err<E>(data:E):Err<E> {
// 		return {
// 			tag:"Err",
// 			data:data
// 		}
// 	}
//
// 	export type Ok<T> = Tag_Data<"Ok",T>;
// 	export function Ok<T>(data:T):Ok<T> {
// 		return {
// 			tag:"Ok",
// 			data:data
// 		}
// 	}
//
// 	export type Result<T,E> = Ok<T> | Err<E>;
//
// 	function Result_match<R,T,E>(r:Result<T, E>
// 	                         ,ok:(t:T)=>R
// 	                         ,err:(e:E)=>R ): R  {
// 		switch (r.tag) {
// 			case "Ok":{
// 				return ok(r.data);
// 			}
// 			case "Err":{
// 				return err(r.data);
// 			}
// 		}
// 	}
// 	function get_ok<T,E>(r:Result<T,E>): T | null{
// 		return Result_match<T|null,T,E>(r,(t)=>t,(e)=>null);
// 	}
// 	function get_err<T,E>(r:Result<T,E>): E | null {
// 		return Result_match<E|null,T,E>(r,(t)=>null,(e)=>e);
// 	}
//
// 	function is_ok<T,E>(r:Result<T,E>):boolean {
// 		return Result_match<boolean,T,E>(r,(t)=>true,(e)=>false);
// 	}
// 	function is_err<T,E>(r:Result<T,E>):boolean {
// 		return Result_match<boolean,T,E>(r,(t)=>false,(e)=>true);
// 	}
//
// 	module Test{
// 		/// 可行哦~
// 		function test_1() {
// 			let a:Result<number, string> = Err("");// nice
// 			// let a:Result<number, string> = Err(1);// mistake:类型不匹配
// 			a = Ok(1);// nice
// 			// a = Ok("");//mistake:类型不匹配
// 		}
//
// 		function test_2() {
// 			let a:Result<number, string> = Err("");// nice
// 			let b = Result_match<boolean,number,string>(a,
// 				(t)=>{
// 					return false
// 				},
// 				(e)=>{
// 					return true
// 				});
// 			console.log(b);
// 		}
//
// 	}
// }
//
// /**
//  * 具有泛型的多类型的 Enum
//  * 发现Result可行后,尝试一下
//  */
// export module Enum{
// 	/**
// 	 * [enum名,enum类型]
// 	 */
// 	export type Name_Type<Name extends string,Type> = [Name,Type];
// 	export type Type_Data<Type  extends string,Data> = {
// 		type:Type,
// 		data:Data
// 	}
// 	export type Enum<T> = T extends Name_Type<infer Type,infer Data>
// 		? Type_Data<Type,Data>
// 		:void;
//
// 	function new_enum<Type extends string,Data>(type:Type,data:Data):Type_Data<Type, Data> {
// 		return {
// 			type:type,
// 			data:data
// 		}
// 	}
//
// 	function enum_match<R,Type extends string,Data,E extends Enum<T>,T
// 		>(t:T,f:{
// 			[type : string]:(data:Data)=>R,// 指定
// 			0:(data:Data)=>R // 穷举
// 		}):R{
// 		let type = t.type;
// 		if(f[type] == undefined){
// 			return f[0](t.data);
// 		}else {
// 			return f[type](t.data);
// 		}
// 	}
//
//
// 	export module Test{
// 		function f() {
// 			// 定义一个枚举
// 			type E<T> = Enum<
// 				["num",number]|
// 				["str",string]|
// 				["ttt",T]|string|boolean>//string|boolean 无效
// 			let a:E<boolean> = new_enum("ttt",false);//nice
// 			// let a:E<boolean> = new_enum("ttt",0);// mistake:类型不匹配
// 			// let a:E<boolean> = new_enum("str",0);// mistake:类型不匹配
//
// 		}
// 		function match() {
// 			type E = Enum<
// 				["num",number]|
// 				["str",string]|
// 				["bool",boolean]>
// 			let a:E = new_enum("bool",false);
// 			switch (a.type){
// 				case "bool":{
// 					let b:boolean = a.data;
// 					// let b:string = a.data;// mistake:类型不匹配
// 				}
// 			}
// 		}
// 		export function e_match() {
// 			type E = Enum<
// 				["num",number]|
// 				["str",string]|
// 				["bool",boolean]>;
// 			let a:E = new_enum("num",0);
// 			a=new_enum("str","abc");
// 			let b = enum_match(a,{
// 				"num":(t)=>{
// 					// let a:string = t;//实际上可以判断出类型错误,但是IDE就是提示 number|string|boolean
// 					let a:number = t;
// 					return 1
// 				},
// 				"str":(t)=>{
// 					let a:string =t;//我日!这里有问题,类型处理有问题啊
// 					return 0
// 				},
// 				0:()=>{
// 					return 0
// 				}
// 			})
//
// 			console.log(b);
// 		}
//
// 	}
// }
